package top.cardone.context.util;

import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import lombok.Setter;
import org.springframework.util.AntPathMatcher;
import org.springframework.util.CollectionUtils;
import org.springframework.util.PathMatcher;
import top.cardone.context.Contexts;

import java.util.Collection;
import java.util.Map;

/**
 * 字符串工具类
 *
 * @author yao hai tao
 */
public class StringUtils extends org.apache.commons.lang3.StringUtils {
	@lombok.Setter
	private static java.util.Map<String, AntPathMatcher> pathMatcherMap = Maps.newConcurrentMap();
	@Setter
	private static Map<String, String> escapeSqlMap;

	static {
		escapeSqlMap = Maps.newHashMap();

		escapeSqlMap.put("'", "''");
		escapeSqlMap.put("\\\\", "\\\\\\\\");
		escapeSqlMap.put("%", "\\\\%");
		escapeSqlMap.put("_", "\\\\_");
	}

	private StringUtils() {
	}

	/**
	 * 返回不为空的字符串
	 *
	 * @param strs 字符串集合
	 * @return 不为空的字符串
	 */
	public static String defaultIfBlank(final String... strs) {
		if (org.apache.commons.lang3.ArrayUtils.isEmpty(strs)) {
			return null;
		}

		for (final String str : strs) {
			if (org.apache.commons.lang3.StringUtils.isNotBlank(str)) {
				return str;
			}
		}

		return null;
	}

	/**
	 * 获取路径
	 *
	 * @param paths 路径集合
	 * @param url   路径
	 * @return 路径
	 */
	public static String getPathForMatch(final java.util.Collection<String> paths, final String url) {
		return getPathForMatch(null, paths, url);
	}

	/**
	 * 获取路径
	 *
	 * @param pathSeparator 路径间隔
	 * @param paths         路径集合
	 * @param url           路径
	 * @return 路径
	 */
	public static String getPathForMatch(String pathSeparator, final Collection<String> paths, final String url) {
		if (CollectionUtils.isEmpty(paths)) {
			return null;
		}

		if (org.apache.commons.lang3.StringUtils.isBlank(url)) {
			return null;
		}

		PathMatcher pathMatcher = StringUtils.getPathMatcher(pathSeparator);

		for (final String path : paths) {
			if (pathMatcher.match(path, url)) {
				return path;
			}
		}

		return null;
	}

	/**
	 * 获取路径比较
	 *
	 * @return 路径比较
	 */
	public static PathMatcher getPathMatcher() {
		return getPathMatcher(null);
	}

	/**
	 * 获取路径比较
	 *
	 * @param pathSeparator 路径间隔
	 * @return 路径比较
	 */
	public static PathMatcher getPathMatcher(String pathSeparator) {
		String newPathSeparator = org.apache.commons.lang3.StringUtils.defaultIfBlank(pathSeparator, AntPathMatcher.DEFAULT_PATH_SEPARATOR);

		AntPathMatcher antPathMatcher = StringUtils.pathMatcherMap.get(newPathSeparator);

		if (antPathMatcher == null) {
			antPathMatcher = new AntPathMatcher(newPathSeparator);

			pathMatcherMap.put(newPathSeparator, antPathMatcher);
		}

		antPathMatcher.setCachePatterns(true);

		return antPathMatcher;
	}

	/**
	 * 比较
	 *
	 * @param paths 路径集合
	 * @param url   路径
	 * @return 比较结果
	 */
	public static boolean matchs(final Collection<String> paths, final String url) {
		if (CollectionUtils.isEmpty(paths)) {
			return false;
		}

		String path = StringUtils.getPathForMatch(paths, url);

		return org.apache.commons.lang3.StringUtils.isNotBlank(path);
	}

	/**
	 * 比较
	 *
	 * @param pathsStr 路径集合
	 * @param url      路径
	 * @return 比较结果
	 */
	public static boolean matchs(final String pathsStr, final String url) {
		final Collection<String> paths = Lists.newArrayList(org.apache.commons.lang3.StringUtils.split(pathsStr, Contexts.comma.stringValue()));

		return StringUtils.matchs(paths, url);
	}

	/**
	 * 批量替换字符串
	 *
	 * @param text           文本
	 * @param replacementMap 替换字符串映射
	 * @return 替换后字符串
	 */
	public static String replaces(String text, Map<String, String> replacementMap) {
		if (isBlank(text)) {
			return text;
		}

		for (Map.Entry<String, String> replacementEntry : replacementMap.entrySet()) {
			text = StringUtils.replace(text, replacementEntry.getKey(), replacementEntry.getValue());
		}

		return text;
	}

	/**
	 * 转义sql字符串
	 *
	 * @param sqlStr sql字符串
	 * @return 转义后sql字符串
	 */
	public static String escapeSql(String sqlStr) {
		return replaces(sqlStr, escapeSqlMap);
	}
}